package com.south.base.test.arithmetic.arrays;

import org.junit.Assert;
import org.junit.Test;

import java.util.Arrays;

/**
 * @author Administrator
 * @date 2020/6/18 14:54
 */
public class Move {
    /**
     * 旋转数组
     * 给定一个数组，将数组中的元素向右移动 k 个位置，其中 k 是非负数。
     */
    @Test
    public void rotate() {
        int[] r = new int[]{1, 2, 3, 4, 5, 6, 7};
        rotate(r, 3);
        Assert.assertArrayEquals(new int[]{5, 6, 7, 1, 2, 3, 4}, r);
        r = new int[]{-1, -100, 3, 99};
        rotate(r, 6);
        Assert.assertArrayEquals(new int[]{3, 99, -1, -100}, r);
        int[][] r2 = new int[][]{{1, 2, 3},
                {4, 5, 6},
                {7, 8, 9}};
        rotate(r2);
        Assert.assertArrayEquals(new int[][]{{7, 4, 1},
                {8, 5, 2},
                {9, 6, 3}}, r2);
    }

    public void rotate(int[] nums, int k) {
        if (nums.length < 2) {
            return;
        }
        int index = 0;
        for (int i = 0; i < k; i++) {
            if (index == 0) {
                index = nums.length - 1;
            } else {
                index--;
            }
        }
        int[] tmp = new int[nums.length - index];
        System.arraycopy(nums, index, tmp, 0, nums.length - index);
        System.arraycopy(nums, 0, nums, nums.length - index, index);
        System.arraycopy(tmp, 0, nums, 0, nums.length - index);
    }

    /**
     * 旋转图像
     * 给定一个 n × n 的二维矩阵表示一个图像。
     * 将图像顺时针旋转 90 度。
     *
     * @param matrix
     */
    public void rotate(int[][] matrix) {
        int[][] f = new int[matrix.length][matrix.length];
        for (int i = 0; i < f.length; i++) {
            f[i] = Arrays.copyOf(matrix[i], matrix.length);
        }
        for (int i = 0; i < matrix.length; i++) {
            for (int j = 0; j < matrix[0].length; j++) {
                matrix[j][matrix.length - 1 - i] = f[i][j];
            }
        }
    }

    /**
     * 移动零
     * 给定一个数组 nums，编写一个函数将所有 0 移动到数组的末尾，同时保持非零元素的相对顺序。
     */
    @Test
    public void moveZeroes() {
        int[] a = new int[]{0, 1, 0, 3, 12};
        moveZeroes(a);
        Assert.assertArrayEquals(new int[]{1, 3, 12, 0, 0}, a);
    }

    public void moveZeroes(int[] nums) {
        int index = 0;
        for (int i = 0; i < nums.length; i++) {
            if (nums[i] != 0) {
                nums[index] = nums[i];
                index++;
            }
        }
        for (; index < nums.length; index++) {
            nums[index] = 0;
        }
    }
}
